package com.jplus.plugins.rpc;

import java.lang.reflect.Field;
import java.util.HashSet;
import java.util.Set;
import java.util.concurrent.atomic.AtomicInteger;

import org.slf4j.Logger;
import org.slf4j.LoggerFactory;

import com.jplus.framework.bean.BeanHandle;
import com.jplus.framework.plugin.Plugin;
import com.jplus.plugins.rpc.annotation.RpcConsumer;
import com.jplus.plugins.rpc.annotation.RpcProvider;
import com.jplus.plugins.rpc.core.RpcClient;
import com.jplus.plugins.rpc.core.RpcService;
import com.jplus.plugins.rpc.core.ZkFactory;

/**
 * RpcPlugin<br>
 * PRC目前支持三种 传输类型：<br>
 * 
 * 1.Socket[二进制流]<br>
 * 2.Netty[二进制流]<br>
 * 3.Http[JSON文本]<依赖web容器><br>
 * 
 * @author Yuanqy
 *
 */
public class RpcPlugin implements Plugin {

	private final Logger logger = LoggerFactory.getLogger(getClass());

	private final RpcClient rpcCli = new RpcClient();
	private final RpcService rpcSer = new RpcService();

	@Override
	public void init() {
		try {
			AtomicInteger aci = new AtomicInteger(0);
			// == 初始化zookeeper连接
			if (ZkFactory.getZK() == null)
				ZkFactory.createConnection(Constant.ZK_ADDRESS, Constant.ZK_SESSION_TIMEOUT);

			Set<Class<?>> rpcServices = new HashSet<Class<?>>();
			Set<Field> rpcClient = new HashSet<Field>();
			for (Class<?> cls : BeanHandle.beanSet) {
				// ==获取服务提供者，只是获取类名
				if (cls.isAnnotationPresent(RpcProvider.class)) {
					rpcServices.add(cls);
					logger.info("\t\t[RpcProvider]{}", cls.getName());
				}
				// ==获取消费者，只是有@RpcConsumer的字段
				Field[] fs = cls.getDeclaredFields();
				for (Field f : fs) {
					f.setAccessible(true);
					if (f.getAnnotation(RpcConsumer.class) != null) {
						rpcClient.add(f);
						aci.addAndGet(1);
						logger.info("\t\t[RpcConsumer]{}", f.getType());
					}
				}
			}
			// ==实例化服务提供者/消费者===
			rpcCli.create(rpcClient);
			rpcSer.create(rpcServices);
			// ==最后开启观察，[观察是给客户端用的，如果没有客户端，就不开启]
			if (aci.get() > 0)
				ZkFactory.watchNode();
		} catch (Exception e) {
			e.printStackTrace();
		}
	}

	@Override
	public void destroy() {
		
		// TODO Auto-generated method stub
		
	}

}
